home *** CD-ROM | disk | FTP | other *** search
/ Personal Computer World 2006 December / PCWDEC06.iso / Software / Trial / Paint Shop Pro XI / Data1.cab / _1665AF6FB28149148BBE2154FD1ED9CD < prev    next >
Encoding:
Text File  |  2006-08-04  |  10.1 KB  |  230 lines

  1. from PSPApp import *
  2. import string
  3. import PSPUtils
  4.  
  5. def ScriptProperties():
  6.     return {
  7.         'Author': u'Corel Corporation',
  8.         'Copyright': u'Copyright (c) 2002-2006 Corel Corporation. All rights reserved.',
  9.         'Description': "Put EXIF camera and exposure information at the bottom of the image.",
  10.         'Host': u'Paint Shop Pro 9',
  11.         'Host Version': u'9.00',
  12.         }
  13.  
  14.  
  15. def Do(Environment):
  16.     ''' This script extracts data from the active document to place a caption at the lower right corner
  17.         of the image.  The caption contains the camera make/model number, aperture and exposure time.
  18.         This does require that the image contain this information to being with - if no EXIF data is
  19.         found it puts up a message box and returns.
  20.  
  21.         The text is placed at the bottom right corner of the image.  To make it easier to read, the area
  22.         around the text is filled with a dark gray.
  23.  
  24.         To isolate the caption and backdrop from the rest of the image, a layer group is created.
  25.         Following execution of the script, three additional layers will be created, placed above the
  26.         layer that was active when the script was run:
  27.         EXIF Caption - the group layer
  28.           EXIF Text - this is a vector layer containing the text we created
  29.           Caption Background - this is a raster layer that is filled with grey around the text
  30.     '''
  31.     if PSPUtils.RequireADoc( Environment ) == App.Constants.Boolean.false:
  32.         return
  33.  
  34.     
  35.     # first extract the EXIF data - if we can't find any just return without changing the image
  36.     ImageInfo = App.Do( Environment, 'ReturnImageInfo', {'GeneralSettings': {'Version': ((9,0,0),1) }} )
  37.     if ImageInfo['ExifMake'] == '' or ImageInfo['ExifModel'] == '' or \
  38.        ImageInfo['ExifFNumber' ] == '' or ImageInfo['ExifExposureTime'] == '':
  39.         App.Do(Environment,  'MsgBox', {
  40.                 'Buttons': App.Constants.MsgButtons.OK, 
  41.                 'Icon': App.Constants.MsgIcons.Stop, 
  42.                 'Text': PSPUtils.NoEXIFData,
  43.                 'GeneralSettings': {'Version': ((9,0,0),1) }
  44.                 })
  45.         return
  46.  
  47.  
  48.     # save any existing selection
  49.     SelSaver = PSPUtils.SaveSelection( Environment, App.TargetDocument )
  50.     
  51.     # assemble the camera string by concatenating the camera make and model.  Some camera
  52.     # manufacturers have the barbaric practice of CAPITALIZING everything in their make and model
  53.     # strings, so convert it to initial caps only for a more civilized appearance
  54.     CaptionTextCamera = unicode(string.capwords( ImageInfo['ExifMake'] + ' ' + ImageInfo[ 'ExifModel' ] ))
  55.     
  56.     # now assemble exposure information by using the aperture and exposure
  57.     Aperture = float(ImageInfo['ExifFNumber'])
  58.     CaptionTextExposure = PSPUtils.ExposureMsg % (Aperture, ImageInfo['ExifExposureTime'].strip())
  59.  
  60.     # first we create a raster layer at 50% opacity as a backdrop for the caption    
  61.     # for now the raster layer is empty - we'll fill it in later
  62.     # the new layer becomes the active layer
  63.     App.Do( Environment, 'NewRasterLayer', {
  64.             'General': {
  65.                 'Opacity': 50, 
  66.                 'Name': PSPUtils.CaptionBackground, 
  67.                 'IsVisible': App.Constants.Boolean.true, 
  68.                 }, 
  69.             'GeneralSettings': {
  70.                 'ExecutionMode': App.Constants.ExecutionMode.Silent,
  71.                 'Version': ((9,0,0),1)
  72.                 }
  73.             })
  74.     
  75.     # create a layer group.  This will place the raster layer in the group
  76.     # the group is the active layer on completion
  77.     App.Do( Environment, 'NewLayerGroup', {
  78.             'General': {
  79.                 'Opacity': 100, 
  80.                 'Name': PSPUtils.EXIFCaption, 
  81.                 }, 
  82.             'GeneralSettings': {
  83.                 'ExecutionMode': App.Constants.ExecutionMode.Silent,
  84.                 'Version': ((9,0,0),1)
  85.                 }
  86.             })
  87.  
  88.     # select the raster layer so that the vector layer gets created above it
  89.     App.Do( Environment, 'SelectLayer', {
  90.             'Path': (0,0,[1],App.Constants.Boolean.false),
  91.             'GeneralSettings': {'Version': ((9,0,0),1) }
  92.             })
  93.     
  94.     # now create a vector layer to put text on - creating the layer will make it active
  95.     App.Do( Environment, 'NewVectorLayer', {
  96.             'General': {
  97.                 'Opacity': 100, 
  98.                 'Name': PSPUtils.EXIFText, 
  99.                 }, 
  100.             'GeneralSettings': {
  101.                 'ExecutionMode': App.Constants.ExecutionMode.Silent,
  102.                 'Version': ((9,0,0),1)
  103.                 }
  104.             })
  105.  
  106.     # Figure out how big the text should be by examining the overall image size.  We'll do a rough
  107.     # scale based on 1000 pixels.  We won't paint text less than 16 point in any event.
  108.     ImageMaxDimension = max(App.TargetDocument.Width, App.TargetDocument.Height)
  109.     TextScaleFactor = max(0.25, float(ImageMaxDimension) / 1000.0)
  110.     TextSize = int(16.0 * TextScaleFactor)
  111.  
  112.     # now place the text - use right justification at the lower right corner of the image.
  113.     # we are placing 16 pixel text, so to leave some room for leading we place the first
  114.     # line of text 24 pixels up from the bottom, and the second will be only 4 pixels up
  115.     # from the bottom.
  116.     # since we use a black backdrop for the text, make the text color white.
  117.     TextPlacementLine1 = (App.TargetDocument.Width - 4 * TextScaleFactor, App.TargetDocument.Height - (24 * TextScaleFactor))
  118.     App.Do( Environment, 'TextEx', {
  119.             'Visibility': True, 
  120.             'CreateAs': App.Constants.CreateAs.Vector, 
  121.             'TextFlow': App.Constants.TextFlow.HorizontalDown, 
  122.             'TextType': App.Constants.TextType.TextBase, 
  123.             'AutoKern': False, 
  124.             'AntialiasStyle': App.Constants.AntialiasEx.Smooth, 
  125.             'Fill': {
  126.                 'Color': (255,255,255), 
  127.                 'Pattern': None, 
  128.                 'Gradient': None, 
  129.                 'Texture': None
  130.                 }, 
  131.             'Font': PSPUtils.CaptionFontName, 
  132.             'PointSize': TextSize, 
  133.             'Start': TextPlacementLine1, 
  134.             'Stroke': None,
  135.             'LineStyle': None,
  136.             'LineWidth':0,
  137.             'SetText': App.Constants.Justify.Right, 
  138.             'Characters': CaptionTextCamera, 
  139.             'GeneralSettings': {
  140.                 'ExecutionMode': App.Constants.ExecutionMode.Silent, 
  141.                 'AutoActionMode': App.Constants.AutoActionMode.Match,
  142.                 'Version': ((9,0,0),1)
  143.                 }
  144.             })
  145.  
  146.     # place the second line of text
  147.     TextPlacementLine2 = (App.TargetDocument.Width - 4 * TextScaleFactor, App.TargetDocument.Height - (4 * TextScaleFactor) )
  148.     App.Do( Environment, 'TextEx', {
  149.             'Visibility': True, 
  150.             'CreateAs': App.Constants.CreateAs.Vector, 
  151.             'TextFlow': App.Constants.TextFlow.HorizontalDown, 
  152.             'TextType': App.Constants.TextType.TextBase, 
  153.             'AutoKern': False, 
  154.             'AntialiasStyle': App.Constants.AntialiasEx.Smooth, 
  155.             'Fill': {
  156.                 'Color': (255,255,255), 
  157.                 'Pattern': None, 
  158.                 'Gradient': None, 
  159.                 'Texture': None
  160.                 }, 
  161.             'Font': PSPUtils.CaptionFontName, 
  162.             'PointSize': TextSize, 
  163.             'Start': TextPlacementLine2, 
  164.             'Stroke': None,
  165.             'LineStyle': None,
  166.             'LineWidth':0,
  167.             'SetText': App.Constants.Justify.Right, 
  168.             'Characters': CaptionTextExposure, 
  169.             'GeneralSettings': {
  170.                 'ExecutionMode': App.Constants.ExecutionMode.Silent, 
  171.                 'AutoActionMode': App.Constants.AutoActionMode.Match,
  172.                 'Version': ((9,0,0),1)
  173.                 }
  174.             })
  175.  
  176.     # we have the text down, but we want to put a backdrop behind it so that the text remains
  177.     # visible.  How big do we make the backdrop?  Who knows, so we just ask the vector layer how
  178.     # big it is
  179.     Result = App.Do( Environment, 'ReturnLayerProperties', {'GeneralSettings': {'Version': ((9,0,0),1) }} )
  180.     TextRectangle = Result[ 'LayerRect' ]
  181.     FillStartPoint = ( TextRectangle[0][0] - (4 * TextScaleFactor), TextRectangle[0][1] - (4 * TextScaleFactor) )
  182.     FillEndPoint = ( App.TargetDocument.Width, App.TargetDocument.Height )
  183.     
  184.     # select the raster layer - it is immediately below the vector layer
  185.     App.Do( Environment, 'SelectLayer', {
  186.             'Path': (0,-1,[],App.Constants.Boolean.false),
  187.             'GeneralSettings': {'Version': ((9,0,0),1) }
  188.             })
  189.  
  190.     # make a selection around the bounding box of the text.  Once we have a selection we'll fill it
  191.     App.Do( Environment, 'Selection', {
  192.             'General': {
  193.                 'Mode': App.Constants.SelectionOperation.Replace, 
  194.                 'Antialias': App.Constants.Boolean.true, 
  195.                 'Feather': 0
  196.                 }, 
  197.             'SelectionShape': App.Constants.SelectionShape.Rectangle, 
  198.             'Start': FillStartPoint, 
  199.             'End': FillEndPoint, 
  200.             'GeneralSettings': {
  201.                 'ExecutionMode': App.Constants.ExecutionMode.Silent,
  202.                 'Version': ((9,0,0),1)
  203.                 }
  204.             })
  205.  
  206.     # now do a flood fill, making sure the point we click on is inside of our selection
  207.     # use a dark grey for the fill so that we can see the text on top of it
  208.     App.Do( Environment, 'Fill', {
  209.             'BlendMode': 0, 
  210.             'MatchMode': 1, 
  211.             'Material': {
  212.                 'Color': (32,32,32), 
  213.                 'Pattern': None, 
  214.                 'Gradient': None, 
  215.                 'Texture': None
  216.                 }, 
  217.             'Opacity': 100, 
  218.             'Point': (FillStartPoint[0] + 1, FillStartPoint[1] + 1), 
  219.             'Tolerance': 20, 
  220.             'GeneralSettings': {
  221.                 'ExecutionMode': App.Constants.ExecutionMode.Silent,
  222.                 'Version': ((9,0,0),1)
  223.                 }
  224.             })
  225.  
  226.     # restore the original selectoin
  227.     SelSaver.RestoreSelection()
  228.     
  229.     # All done!
  230.